package com.link.base.base.email.emailutils;

import org.apache.commons.lang.StringUtils;


import javax.activation.DataHandler;
import javax.activation.FileDataSource;
import javax.mail.*;
import javax.mail.internet.*;
import java.io.File;
import java.util.*;
import java.util.Map.Entry;

/**
 * @author weixuan
 */
public class SendMail {

    /**
     * 一个有规则的map，用作嵌入图片
     */
    Map<String, String> map;
    /**
     * 存放附件
     */
    List<String> list;
    /**
     * 邮件服务器主机名
     */
    private String smtp = "";
    /**
     * 邮件传输协议
     */
    private String protocol = "";
    /**
     * 登录用户名
     */
    private String username = "";
    /**
     * 登录密码
     */
    private String pas = "";
    /**
     * 发件人地址
     */
    private String from = "";
    /**
     * 收件人地址
     */
    private String to = "";
    /**
     * 抄送人地址
     */
    private String toCc = "";
    /**
     * 密送人地址
     */
    private String toBCc = "";
    /**
     * 邮件主题
     */
    private String subject = "";
    /**
     * 邮件内容
     */
    private String body = "";
    /**
     * 邮件代理服务授权码
     */
    private String emailAuthSecret = "";
    private List<File> attchmentList;

    public SendMail(Map<String, String> map, List<String> filelist, Map<String, String> image) {
        this.smtp = map.get("smtp");
        this.protocol = map.get("protocol");
        this.username = map.get("username");
        this.pas = map.get("pas");
        this.from = map.get("from");
        this.to = map.get("to");
        this.toCc = map.get("toCc");
        this.toBCc = map.get("toBCc");
        this.subject = map.get("subject");
        this.body = map.get("body");
        this.emailAuthSecret = map.get("emailAuthSecret");

        this.list = filelist;
        this.map = image;
    }

    public SendMail(Map<String, String> map, List<File> filelist) {
        this.smtp = map.get("smtp");
        this.protocol = map.get("protocol");
        this.username = map.get("username");
        this.pas = map.get("pas");
        this.from = map.get("from");
        this.to = map.get("to");
        this.toCc = map.get("toCc");
        this.toBCc = map.get("toBCc");
        this.subject = map.get("subject");
        this.body = map.get("body");
        this.emailAuthSecret = map.get("emailAuthSecret");

        this.attchmentList = filelist;
    }

    /**
     * 新浪代理邮件发送
     * @author
     * @throws Exception
     */
    public void send() throws Exception {
        Properties pros = new Properties();
        pros.setProperty("mail.transport.protocol", this.protocol);
        pros.setProperty("mail.host", this.smtp);
        pros.put("mail.smtp.auth", "true");
        MySendMailAuthenticator ma = new MySendMailAuthenticator(this.username, this.pas);
        Session session = Session.getInstance(pros, ma);
        session.setDebug(false);
        MimeMessage msg = createMessage(session);
        // 发送邮件
        Transport ts = session.getTransport();
        ts.connect();
        if (StringUtils.isNotBlank(to)) {
            ts.sendMessage(msg, msg.getRecipients(Message.RecipientType.TO));
        }
        if (StringUtils.isNotBlank(toCc)) {
            ts.sendMessage(msg, msg.getRecipients(Message.RecipientType.CC));
        }
        if (StringUtils.isNotBlank(toBCc)) {
            ts.sendMessage(msg, msg.getRecipients(Message.RecipientType.BCC));
        }
        ts.close();
    }

    @SuppressWarnings("unused")
    public MimeMessage createMessage(Session session) throws Exception {

        MimeMessage message = new MimeMessage(session);
        message.setFrom(new InternetAddress(this.from));

        //邮件接收人
        if (StringUtils.isNotBlank(this.to)) {
            InternetAddress[] address = getToEmailAddr(this.to);
            if (address != null && address.length > 0) {
                message.setRecipients(Message.RecipientType.TO, address);
            }
        }

        // 邮件抄送人
        if (StringUtils.isNotBlank(this.toCc)) {
            InternetAddress[] ccAdresses = getToEmailAddr(this.toCc);
            if (ccAdresses != null && ccAdresses.length > 0) {
                message.setRecipients(Message.RecipientType.CC, ccAdresses);
            }
        }

        //邮件密送人
        if (StringUtils.isNotBlank(this.toBCc)) {
            InternetAddress[] bccAdresses = getToEmailAddr(this.toBCc);
            if (bccAdresses != null && bccAdresses.length > 0) {
                message.setRecipients(Message.RecipientType.BCC, bccAdresses);
            }
        }

        message.setSubject(this.subject);

        MimeMultipart allMultipart = new MimeMultipart();

        //创建代表邮件正文和附件的各个MimeBodyPart对象
        MimeBodyPart contentpart = createContent(this.body);
        allMultipart.addBodyPart(contentpart);


        //web端上传的附件
        for (int i = 0; i < attchmentList.size(); i++) {
            allMultipart.addBodyPart(createAttachment(attchmentList.get(i)));
        }
        //设置整个邮件内容为最终组合出的MimeMultipart对象
        message.setContent(allMultipart);
        message.saveChanges();
        return message;
    }

    @SuppressWarnings({"rawtypes", "unchecked"})
    public MimeBodyPart createContent(String body) throws Exception {
        MimeMultipart contentMultipart = new MimeMultipart("related");

        //创建用于保存HTML正文的MimeBodyPart对象，并将它保存到MimeMultipart中
        MimeBodyPart htmlbodypart = new MimeBodyPart();
        htmlbodypart.setContent(this.body, "text/html;charset=UTF-8");
        contentMultipart.addBodyPart(htmlbodypart);

        //处理邮件内置图片
        if (map != null && map.size() > 0) {
            Set<Entry<String, String>> set = map.entrySet();
            for (Iterator iterator = set.iterator(); iterator.hasNext(); ) {
                Entry<String, String> entry = (Entry<String, String>) iterator.next();

                //创建用于保存图片的MimeBodyPart对象，并将它保存到MimeMultipart中
                MimeBodyPart gifBodyPart = new MimeBodyPart();
                //图片所在的目录的绝对路径
                FileDataSource fds = new FileDataSource(entry.getValue());

                gifBodyPart.setDataHandler(new DataHandler(fds));
                //cid的值
                gifBodyPart.setContentID(entry.getKey());
                contentMultipart.addBodyPart(gifBodyPart);
            }
        }

        //创建代表组合Mime消息的MimeMultipart对象，将该MimeMultipart对象保存到MimeBodyPart对象
        MimeBodyPart contentPart = new MimeBodyPart();
        //将MimeMultipart对象保存到MimeBodyPart对象
        contentPart.setContent(contentMultipart);
        return contentPart;
    }

    /**
     * 创建保存附件的MimeBodyPart对象，并加入附件内容和相应的信息
     * @author
     * @param filename
     * @return
     * @throws Exception
     *
     */
    public MimeBodyPart createAttachment(String filename) throws Exception {
        //创建保存附件的MimeBodyPart对象，并加入附件内容和相应的信息
        MimeBodyPart attachPart = new MimeBodyPart();
        FileDataSource fsd = new FileDataSource(filename);
        attachPart.setDataHandler(new DataHandler(fsd));
        attachPart.setFileName(fsd.getName());
        return attachPart;
    }

    /**
     * 接收web端上传的附件，添加到邮件附件
     * @author yipeng.zhu@hand-china.com
     * @param file 网页上传的附件
     * @return
     * @throws
     * @date 2019/2/25 11:25
     * @version 1.0
     */
    public MimeBodyPart createAttachment(File file) throws Exception {
        //创建保存附件的MimeBodyPart对象，并加入附件内容和相应的信息
        MimeBodyPart attachPart = new MimeBodyPart();
        attachPart.attachFile(file);
        attachPart.setFileName(MimeUtility.encodeText(file.getName()));
        return attachPart;
    }

    /**
     * 获取邮件接收地址
     * @author
     * @param addrStr
     * @return
     * @throws AddressException
     *
     */
    public InternetAddress[] getToEmailAddr(String addrStr) throws AddressException {
        String[] arr = addrStr.split(",");
        int receiverCount = arr.length;
        InternetAddress[] address = new InternetAddress[receiverCount];
        for (int i = 0; i < receiverCount; i++) {
            if (arr[i] != null && !"".equals(arr[i])) {
                address[i] = new InternetAddress(arr[i]);
            }
        }
        return address;
    }

    /**
     * QQ代理邮件服务器 发送邮件
     * @author yipeng.zhu@hand-china.com
     * @param
     * @return
     * @throws
     * @date 2018/12/18 9:19
     */
    public void sendQqMail() throws Exception {
        String sportType = "smtp";
        Properties props = new Properties();
        props.put("mail.smtp.host", smtp);
        //发件人使用发邮件的电子信箱服务器
        props.put("mail.password", emailAuthSecret);
        props.put("mail.transport.protocol", "smtp");
        props.setProperty("mail.debug", "true");
        //这样才能通过验证
        props.put("mail.smtp.auth", "true");
        //如果没有加入进去，qq邮箱会验证不成功，一直报503错误
        props.put("mail.smtp.socketFactory.class", "javax.net.ssl.SSLSocketFactory");
        props.put("mail.smtp.ssl.checkserveridentity", true);
        props.put("mail.smtp.port", "465");
        props.put("mail.smtp.socketFactory.port", "465");
        //获得默认的session对象
        Session mailSession = Session.getInstance(props);
        mailSession.setDebug(false);
        MimeMessage mimeMessage = createMessage(mailSession);
        // 发送邮件
        Transport ts = mailSession.getTransport(sportType);
        ts.connect(smtp, from, emailAuthSecret);

        if (StringUtils.isNotBlank(toCc)) {
            ts.sendMessage(mimeMessage, mimeMessage.getRecipients(Message.RecipientType.CC));
        }
        if (StringUtils.isNotBlank(toBCc)) {
            ts.sendMessage(mimeMessage, mimeMessage.getRecipients(Message.RecipientType.BCC));
        }
        if (StringUtils.isNotBlank(to)) {
            ts.sendMessage(mimeMessage, mimeMessage.getRecipients(Message.RecipientType.TO));
        }
        ts.close();
    }

    /**
     * 网易邮件代理服务器 发送邮件
     * @author yipeng.zhu@hand-china.com
     * @param
     * @return
     * @throws
     * @date 2019/2/20 9:19
     */
    public void sendNetEaseMail() throws Exception {
        String sportType = "smtp";
        Properties props = new Properties();
        props.put("mail.smtp.host", smtp);
        //发件人使用发邮件的电子信箱服务器
        props.put("mail.password", emailAuthSecret);
        props.put("mail.transport.protocol", "smtp");
        props.setProperty("mail.debug", "true");
        //这样才能通过验证
        props.put("mail.smtp.auth", "true");
        props.put("mail.smtp.socketFactory.port", "25");
        //获得默认的session对象
        Session session = Session.getInstance(props);
        session.setDebug(false);
        MimeMessage mimeMessage = createMessage(session);

        // 发送邮件
        Transport ts = session.getTransport(sportType);
        ts.connect(smtp, from, emailAuthSecret);
        if (StringUtils.isNotBlank(toCc)) {
            ts.sendMessage(mimeMessage, mimeMessage.getRecipients(Message.RecipientType.CC));
        }
        if (StringUtils.isNotBlank(to)) {
            ts.sendMessage(mimeMessage, mimeMessage.getRecipients(Message.RecipientType.TO));
        }

        if (StringUtils.isNotBlank(toBCc)) {
            ts.sendMessage(mimeMessage, mimeMessage.getRecipients(Message.RecipientType.BCC));
        }
        ts.close();
    }
}




